package org.samcolon.eeexplore.demo;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.lang.Console;

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.stream.Collectors;

import cn.hutool.core.thread.ThreadUtil;
import lombok.Data;
import org.samcolon.eeexplore.entity.*;

/**
 * @Description: 异步操作
 * @author: Sam.zhang
 * @date: 2021/11/4 - 10:49
 */
public class AsyncDemo {
    public static void main(String[] args) throws ExecutionException, InterruptedException {
        CompletableFuture<Void> future = CompletableFuture.runAsync(() -> {
            try {
                Thread.sleep(2000L);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            Console.log("异步运行成功！");
        });
        Console.log("主线程运行完成");
        future.thenAccept(e -> Console.log("子线程运行完成"));
        future.get();

        List<AsyncTestBean> list = fillBean(10);

        AtomicInteger index = new AtomicInteger(1);
        List<CompletableFuture<AsyncTestBean>> collect = list.stream()
                .map(e -> CompletableFuture.completedFuture(e).thenApplyAsync(x -> {
                    int i = index.addAndGet(1);
            Console.log("start int {}", i);
            if(i % 2 == 0){
                ThreadUtil.sleep(2000L);
            }
            x.setValue(i);
            return x;
        })).collect(Collectors.toList());

        CompletableFuture.allOf(collect.toArray(new CompletableFuture[collect.size()])).join();
        Console.log(list);

//        CompletableFuture<Integer> future2 = CompletableFuture.supplyAsync(() -> {
//            int i = 0;
//            return i + 1;
//        });
//        CompletableFuture<Integer> future3 = CompletableFuture.supplyAsync(() -> {
//            int i = 0;
//            return i + 1;
//        });
    }
    private static List<AsyncTestBean> fillBean(int num){
        List<AsyncTestBean> list = new ArrayList<>();
        for (int i = 1; i <= num; i++) {
            AsyncTestBean bean = new AsyncTestBean();
            bean.setId(i);
            list.add(bean);
        }
        return list;
    }
}

@Data
class AsyncTestBean{
    private int id;

    private int value;
}